package pe.edu.upc.dai.grupovictor.dao.impl;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
import pe.edu.upc.dai.grupovictor.dao.InscripcionDao;
import pe.edu.upc.dai.grupovictor.dao.util.ConnectionUtils;
import pe.edu.upc.dai.grupovictor.dao.util.DaoException;
import pe.edu.upc.dai.grupovictor.model.Alumno;
import pe.edu.upc.dai.grupovictor.model.Ciclo;
import pe.edu.upc.dai.grupovictor.model.Curso;
import pe.edu.upc.dai.grupovictor.model.DetalleSistemaEvaluacion;
import pe.edu.upc.dai.grupovictor.model.Inscripcion;
import pe.edu.upc.dai.grupovictor.model.NotaCurso;
import pe.edu.upc.dai.grupovictor.model.Profesor;
import pe.edu.upc.dai.grupovictor.model.ProgramaCurso;
import pe.edu.upc.dai.grupovictor.model.TipoEvaluacion;

public class InscripcionDaoImpl implements InscripcionDao {

    private Connection connection;

    public void iniciarConnection(Connection connection) {
        this.connection = connection;
    }

    public Inscripcion seleccionarPorPrimaryKey(Long id) {
        throw new UnsupportedOperationException("Not supported yet.");
    }

    public Inscripcion seleccionarPorNombre(String nombre) {
        throw new UnsupportedOperationException("Not supported yet.");
    }

    public void insertar(Inscripcion ciclo) {
        throw new UnsupportedOperationException("Not supported yet.");
    }

    public void actualizar(Inscripcion inscrito) {
        PreparedStatement st = null;
        try {

            st = connection.prepareStatement("" +
                    "UPDATE INSCRIPCION I  " +
                    "SET I.NOTA_FINAL = ?,  " +
                    "    I.NOTA_PARCIAL = ?  " +
                    "WHERE I.ID_SECCION = ?  " +
                    "AND I.ID_ALUMNO = ?    " );

            st.setFloat(1, inscrito.getNotaFinal());
            st.setFloat(2, inscrito.getNotaParcial());
            st.setFloat(3, inscrito.getIdSeccion().getIdSeccion());
            st.setFloat(4, inscrito.getIdAlumno().getIdAlumno());

            st.execute();

        } catch (SQLException e) {
            ConnectionUtils.rollback(connection);
            throw new DaoException(e);
        } finally {
            ConnectionUtils.closeStatement(st);
        }
    }

    public void eliminar(Inscripcion ciclo) {
        throw new UnsupportedOperationException("Not supported yet.");
    }

    public List<Inscripcion> seleccionarTodosBySeccion(ProgramaCurso seccion, TipoEvaluacion tipoEval) {
        Connection connection = null;
        PreparedStatement st = null;
        ResultSet rs = null;
        Inscripcion inscripcion = null;
        List<Inscripcion> lista = new ArrayList<Inscripcion>();
        try {
            connection = ConnectionUtils.getConnection();
            String sql = "" +
                    "SELECT I.ID_INSCRIPCION,I.NOTA_FINAL,I.NOTA_PARCIAL, " +
                    "       A.ID_ALUMNO,A.CODIGO_ALUMNO,A.NOMBRE_ALUMNO, " +
                    "       T.ID_SECCION,T.CODIGO_SECCION, " +
                    "       P.ID_PROFESOR,P.CO_PROFESOR,P.NOMBRE_PROFESOR, " +
                    "       CI.ID_CICLO,CI.CODIGO_EXTERNO,CI.NOMBRE_CICLO, " +
                    "       CU.ID_CURSO,CU.CODIGO_CURSO,CU.NOMBRE_CURSO, " +
                    "       NC.ID_NOTA_CURSO,NC.NOTA,DSE.PESO_EVALUACION, " +
                    "       TE.ID_TIPO_EVALUACION,TE.NOMBRE_TIPO_EVALUACION, " +
                    "       DSE.ID_DETALLE " +
                    "FROM INSCRIPCION I " +
                    "JOIN ALUMNO A ON I.ID_ALUMNO = A.ID_ALUMNO " +
                    "JOIN PROGRAMA_CURSO T ON I.ID_SECCION = T.ID_SECCION " +
                    "JOIN PROFESOR P ON T.ID_PROFESOR = P.ID_PROFESOR " +
                    "JOIN CURSO CU ON T.ID_CURSO = CU.ID_CURSO " +
                    "JOIN CICLO CI ON T.ID_CICLO = CI.ID_CICLO " +
                    "JOIN SISTEMA_EVALUACION SE ON SE.ID_CICLO = T.ID_CICLO AND SE.ID_CURSO = T.ID_CURSO " +
                    "JOIN DETALLE_SISTEMA_EVALUACION DSE ON DSE.ID_SISTEMA_EVALUACION = SE.ID_SISTEMA_EVALUACION " +
                    "LEFT JOIN NOTA_CURSO NC ON NC.ID_ALUMNO = A.ID_ALUMNO AND NC.ID_SECCION = I.ID_SECCION AND NC.ID_TIPO_EVALUACION = DSE.ID_TIPO_EVALUACION " +
                    "LEFT JOIN TIPO_EVALUACION TE ON DSE.ID_TIPO_EVALUACION = TE.ID_TIPO_EVALUACION " +
                    "WHERE T.ID_SECCION = ? " +
                    "AND DSE.ID_TIPO_EVALUACION = ? " +
                    "ORDER BY A.NOMBRE_ALUMNO ";

            //System.out.println("sql: " + sql);
            st = connection.prepareStatement(sql);

            st.setLong(1, seccion.getIdSeccion());
            st.setLong(2, tipoEval.getIdTipoEvaluacion());
            rs = st.executeQuery();
            while (rs.next()) {
                inscripcion = mapResultSet(rs);
                lista.add(inscripcion);
            }
        } catch (SQLException e) {
            e.printStackTrace();
            throw new DaoException(e);
        } finally {
            ConnectionUtils.closeResultSet(rs);
            ConnectionUtils.closeStatement(st);
            ConnectionUtils.closeConnection(connection);
        }
        return lista;
    }

    private Inscripcion mapResultSet(ResultSet rs) throws SQLException {
        Profesor profesor = new Profesor();
        profesor.setIdProfesor(rs.getLong("ID_PROFESOR"));
        profesor.setCoProfesor(rs.getString("CO_PROFESOR"));
        profesor.setNombreProfesor(rs.getString("NOMBRE_PROFESOR"));

        Ciclo ciclo = new Ciclo();
        ciclo.setCodigoExterno(rs.getString("CODIGO_EXTERNO"));
        ciclo.setIdCiclo(rs.getLong("ID_CICLO"));
        ciclo.setNombreCiclo(rs.getString("NOMBRE_CICLO"));

        Curso curso = new Curso();
        curso.setCodigoCurso(rs.getString("CODIGO_CURSO"));
        curso.setIdCurso(rs.getLong("ID_CURSO"));
        curso.setNombreCurso(rs.getString("NOMBRE_CURSO"));

        ProgramaCurso programaCurso = new ProgramaCurso();
        programaCurso.setCodigoSeccion(rs.getString("CODIGO_SECCION"));
        programaCurso.setIdSeccion(rs.getLong("ID_SECCION"));
        programaCurso.setIdCiclo(ciclo);
        programaCurso.setIdCurso(curso);
        programaCurso.setIdProfesor(profesor);

        Alumno alumno = new Alumno();
        alumno.setIdAlumno(rs.getLong("ID_ALUMNO"));
        alumno.setCodigoAlumno(rs.getString("CODIGO_ALUMNO"));
        alumno.setNombreAlumno(rs.getString("NOMBRE_ALUMNO"));

        TipoEvaluacion tipoEvaluacion = new TipoEvaluacion();
        tipoEvaluacion.setIdTipoEvaluacion(rs.getLong("ID_TIPO_EVALUACION"));
        tipoEvaluacion.setNombreTipoEvaluacion(rs.getString("NOMBRE_TIPO_EVALUACION"));

        NotaCurso nota = new NotaCurso();
        nota.setIdNotaCurso(rs.getLong("ID_NOTA_CURSO"));
        nota.setNota(rs.getFloat("NOTA"));
        nota.setPeso(rs.getFloat("PESO_EVALUACION"));
        nota.setIdAlumno(alumno);
        nota.setIdSeccion(programaCurso);
        nota.setIdTipoEvaluacion(tipoEvaluacion);

        DetalleSistemaEvaluacion detalle = new DetalleSistemaEvaluacion();
        detalle.setIdDetalle(rs.getLong("ID_DETALLE"));

        Inscripcion inscripcion = new Inscripcion();
        inscripcion.setIdInscripcion(rs.getLong("ID_INSCRIPCION"));
        inscripcion.setNotaFinal(rs.getFloat("NOTA_FINAL"));
        inscripcion.setNotaParcial(rs.getFloat("NOTA_PARCIAL"));
        inscripcion.setIdSeccion(programaCurso);
        inscripcion.setIdAlumno(alumno);
        inscripcion.setIdNotaCurso(nota);
        inscripcion.setDetalleSistemaEvaluacion(detalle);

        return inscripcion;
    }
}
